package com.apes.pi.service;

import com.apes.framework.api.DomainService;
import com.apes.framework.api.SpringManager;
import com.apes.framework.plugin.esb.api.SimpleRequest;
import com.apes.framework.plugin.event.EventConst;
import com.apes.framework.plugin.event.Listener;
import com.apes.pi.model.Pipe;
import com.apes.pi.model.QueueReceiver;
import com.apes.pi.parser.QueueCacheManager;
import com.apes.pi.repository.PipeRepository;
import com.apes.pi.repository.QueueReceiverRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.List;

/**
 * 队列
 *
 * @author wuq
 * @create 2019-10-22 16:18
 */
@Service("queueReceiverService")
public class QueueReceiverService extends DomainService {

    @Autowired
    QueueReceiverRepository queueReceiverRepository;
    @Autowired
    PipeRepository pipeRepository;

    public QueueReceiver create(SimpleRequest request){
        QueueReceiver queueReceiver = request.getO(QueueReceiver.class);
        String queueReceiverId = queueReceiver.getQueue().getId() + "." + queueReceiver.getReceiver().getId();
        queueReceiver.setId(queueReceiverId);
        queueReceiver = queueReceiverRepository.saveAndFlush(queueReceiver);
        queueReceiver.setBeforePipes(request.getA("beforePipes", Pipe.class));
        queueReceiver.setAfterPipes(request.getA("afterPipes", Pipe.class));
        queueReceiver = save(queueReceiver);
        SpringManager.getBean(QueueCacheManager.class).addQueueReceiver(queueReceiver);
        return queueReceiver;
    }

    public QueueReceiver save(QueueReceiver queueReceiver){
        String queueReceiverId = queueReceiver.getId();
        pipeRepository.deleteByParent(queueReceiverId);
        // 前置拦截器
        List<Pipe> beforePipe = queueReceiver.getBeforePipes();
        if (beforePipe != null) {
            beforePipe.stream().forEach( pipe -> {
                pipe.setParent(queueReceiverId);
                pipeRepository.saveAndFlush(pipe);
            });
        }

        // 后置拦截器
        List<Pipe> afterPipe = queueReceiver.getAfterPipes();
        if (afterPipe != null) {
            afterPipe.stream().forEach( pipe -> {
                pipe.setParent(queueReceiverId);
                pipeRepository.saveAndFlush(pipe);
            });
        }
        return queueReceiverRepository.findOne(queueReceiver.getId());
    }

    public QueueReceiver update(SimpleRequest request){
        QueueReceiver queueReceiver = request.getO(QueueReceiver.class);
        queueReceiver = queueReceiverRepository.saveAndFlush(queueReceiver);
        queueReceiver.setBeforePipes(request.getA("beforePipes", Pipe.class));
        queueReceiver.setAfterPipes(request.getA("afterPipes", Pipe.class));
        queueReceiver = save(queueReceiver);
        SpringManager.getBean(QueueCacheManager.class).addQueueReceiver(queueReceiver);
        return queueReceiver;
    }

    public String delete(SimpleRequest request){
        QueueReceiver queueReceiver = request.getO(QueueReceiver.class);
        // 删除管道数据
        String receiverId = queueReceiver.getId();
        pipeRepository.deleteByParent(receiverId);
        queueReceiverRepository.delete(queueReceiver);
        SpringManager.getBean(QueueCacheManager.class).removeQueueReceiver(queueReceiver.getId());
        return "删除成功";
    }

    @Listener(topic = EventConst.POST_LOAD_EVENT)
    public void postUpdate(SimpleRequest request) {
        Object entity = request.getData();
        if(entity instanceof QueueReceiver){
            QueueReceiver queueReceiver = (QueueReceiver) entity;
            String queueId = queueReceiver.getId();
            List<Pipe> pipes = pipeRepository.findByParentOrderById(queueId);

            List<Pipe> beforePipes = new ArrayList<>();
            List<Pipe> afterPipes = new ArrayList<>();

            pipes.stream().forEach( pipe -> {
                if ( "before".equals(pipe.getPosition()) ) {
                    beforePipes.add(pipe);
                } else {
                    afterPipes.add(pipe);
                }
            });

            queueReceiver.setBeforePipes(beforePipes);
            queueReceiver.setAfterPipes(afterPipes);
        }
    }
}
